<?php

namespace app\api\controller;

use app\admin\model\Banner;
use app\admin\model\Column;
use app\admin\model\Contact;
use app\admin\model\gift\Categorys;
use app\admin\model\gift\Goods;
use app\admin\model\gift\Introduce;
use app\admin\model\Levels;
use app\admin\model\Mail;
use app\admin\model\Menus;
use app\admin\model\shop\Message;
use app\admin\model\sign\Rule;
use app\admin\model\Tables;
use app\api\model\Lineup;
use app\api\model\Order;
use app\api\model\SignList;
use app\api\model\UserSignscoreLog;
use app\common\controller\Api;
use app\common\model\ScoreLog;
use think\Db;
use app\common\model\User;
use think\Exception;
use think\helper\Time;

/**
 * 首页接口
 */
class Index extends Api
{
    protected $noNeedLogin = ['*'];
    protected $noNeedRight = ['*'];

    /**
     * Notes: app 版本号
     * User: chenLei
     * Date: 9/12/25
     */
    public function version()
    {
        $app_version = config('site.app_version');
        $this->success('success', ['app_version' => $app_version]);
    }

    /**
     * 店铺信息
     * @ApiReturnParams   (name="manager", type="text", required=true, description="店长")
     * @ApiReturnParams   (name="qrcode", type="text", required=true, description="二维码")
     */
    public function index()
    {
        $res = Message::all();
        $this->success('成功', $res);
    }

    /**
     * 查找店铺信息
     * @ApiMethod (POST)
     * @ApiParams   (name="id", type="string", required=true, description="id")
     * @ApiReturnParams   (name="manager", type="text", required=true, description="店长")
     * @ApiReturnParams   (name="qrcode", type="text", required=true, description="二维码")
     */
    public function find_shop()
    {
        $id = input('post.id');
        $res = Message::where(['id' => $id])->find();
        $this->success('成功', $res);
    }

    /**
     * 轮播图
     * @ApiReturnParams   (name="type", type="text", required=true, description="1详情页2tab页")
     * @ApiReturnParams   (name="href", type="text", required=true, description="链接")
     */
    public function banner()
    {
        $shop_id = $this->request->header('shopid', 1);
        $res = Banner::where(['shop_id' => $shop_id])->select();
        $this->success('成功', $res);
    }

    /**
     * 轮播图下列表
     * @ApiReturnParams   (name="type", type="text", required=true, description="1详情页2tab页")
     * @ApiReturnParams   (name="href", type="text", required=true, description="链接")
     */
    public function collumn()
    {
        $shop_id = $this->request->header('shopid', 1);
        $res = Column::where(['shop_id' => $shop_id])->order('id asc')->select();
        $this->success('成功', $res);
    }

    /**
     * 站内信
     * @ApiMethod (POST)
     * @ApiParams   (name="type", type="string", required=true, description="1Mbr2Platform")
     * @ApiReturnParams   (name="type", type="text", required=true, description="链接")
     * @ApiReturnParams   (name="jump", type="text", required=true, description="跳转方式1详情内容2指定页面")
     * @ApiReturnParams   (name="is_read", type="text", required=true, description="是否已读0未读1已读")
     * @ApiReturnParams   (name="content", type="text", required=true, description="内容")
     * @ApiReturnParams   (name="subtitle", type="text", required=true, description="描述")
     * @ApiReturnParams   (name="page_type", type="text", required=true, description="1内页2tab")
     */
    public function mail()
    {
        $shop_id = $this->request->header('shopid', 1);
        $type = input('post.type', 1);
        $where['shop_id'] = $shop_id;
        $where['type'] = $type;
        $where['user_id'] = ['IN', [0, $this->auth->id]];
        $res = Mail::where($where)->order('id desc')->select();
        foreach ($res as &$value) {
            $value['is_read'] = 0;
            $is_read = Db::name('mail_read')->where(['user_id' => $this->auth->id, 'mail_id' => $value['id']])->find();
            if ($is_read) {
                $value['is_read'] = 1;
            }
        }
        $this->success('成功', $res);
    }

    /**
     * 已读站内信
     * @ApiMethod (POST)
     * @ApiParams   (name="id", type="string", required=true, description="站内信id")
     */
    public function read_mail()
    {
        $id = input('post.id');
        Db::name('mail_read')->insert(['user_id' => $this->auth->id, 'mail_id' => $id]);
        $this->success('成功');
    }

    /**
     * 菜单
     */
    public function menu()
    {
        $shop_id = $this->request->header('shopid', 1);
        $res = Menus::where(['shop_id' => $shop_id])->find();
        $this->success('成功', $res);
    }

    /**
     * 礼品介绍
     */
    public function gift_introduce()
    {
        $res = Introduce::all();
        $this->success('成功', $res);
    }

    /**
     * 礼品分类
     */
    public function gift_categorys()
    {
        $shop_id = $this->request->header('shopid', 1);
        $res = Categorys::where(['shop_id' => $shop_id])->order('id desc')->select();
        $this->success('成功', $res);
    }

    /**
     * 礼品列表
     * @ApiMethod (POST)
     * @ApiParams   (name="categorys_id", type="string", required=true, description="分类id")
     * @ApiReturnParams   (name="name", type="text", required=true, description="名称")
     * @ApiReturnParams   (name="score", type="text", required=true, description="积分")
     * @ApiReturnParams   (name="validity", type="text", required=true, description="时效")
     * @ApiReturnParams   (name="lables", type="text", required=true, description="标签")
     * @ApiReturnParams   (name="content", type="text", required=true, description="详情")
     */
    public function goods_list()
    {
        $shop_id = $this->request->header('shopid', 1);
        $data = Categorys::order('id dec')->select();
        foreach ($data as &$value) {
            $value['goods'] = Goods::where(['shop_id' => $shop_id, 'categorys_id' => $value['id']])->order('id desc')->select();
        }
        $this->success('成功', $data);
    }

    /**
     * 礼品详情
     * @ApiMethod (POST)
     * @ApiParams   (name="id", type="string", required=true, description="id")
     */
    public function goods_detail()
    {
        $id = input('post.id');
        $res = Goods::where(['id' => $id])->find();
        $res['lables'] = explode(',', $res['lables']);
        $this->success('成功', $res);
    }


    /**
     * 兑换礼品
     * @ApiMethod (POST)
     * @ApiParams   (name="id", type="string", required=true, description="id")
     */
    public function exchange_goods()
    {
        $id = input('post.id');
        $res = Goods::where(['id' => $id])->find();
        $user = User::where(['id' => $this->auth->id])->find();
        if ($res['score'] > $user['score']) {
            $this->error('Insufficient points');
        }
        $orderModel = new Order();
        if (in_array($res['categorys_id'], [1, 2])) { // Coupons and products
            if ($res['level'] > $user['level']) {
                $this->error('You cannot redeem gifts with a higher level than your own');
            }
        } else if ($res['categorys_id'] == 3) {  // Monthly exchange
            if ($user['level'] < 3) {
                $this->error('You do not have permission to exchange monthly items');
            }
            if ($orderModel->checkCycle($user['id'])) {
                $this->error('This month’s redemption has already been used.');
            }
        } else if ($res['categorys_id'] == 4) {
            if ($user['level'] < 4) {
                $this->error('You do not have permission to exchange weekly items');
            }
            if ($orderModel->checkCycle($user['id'], 'week')) {
                $this->error('This week’s redemption has already been used.');
            }
        }

        $order_sn = createOrderNo();
        if ($res['validity']) {
            $expire_time = strtotime('+' . $res['validity'] . 'days');
        } else {
            $expire_time = strtotime('+10 year');
        }

        Db::startTrans();
        try {
            $time = time();
            $order_data = [
                'order_sn' => $order_sn,
                'shop_id' => $res['shop_id'],
                'user_id' => $this->auth->id,
                'goods_info' => json_encode($res, 256),
                'score' => $res['score'],
                'name' => $res['name'],
                'validity' => $res['validity'],
                'lables' => $res['lables'],
                'content' => $res['content'],
                'image' => $res['image'],
                'categorys_id' => $res['categorys_id'],
                'expire_time' => $expire_time ?? '',
                'qrcode' => (new \app\api\controller\User())->qrcode($order_sn),
                'create_time' => $time,
                'update_time' => $time,
            ];
//            switch ($res['categorys_id']) {
//                case 1: // 优惠金额逻辑判断
//                    $order_data['money'] = $res['money'];
//                    break;
//                case 2: // 抵扣商品逻辑判断
//                    $order_data['goods_id'] = $res['goods_id'];
//                    break;
//                default:
//                    break;
//            }
            $order_id = Order::insertGetId($order_data);

            if ($res['score'] > 0) {
                $end_score = $user['score'] - $res['score'];
                $user->score = $end_score;
                ScoreLog::create([
                    'user_id' => $this->auth->id,
                    'score' => $res['score'],
                    'before' => $user['score'],
                    'after' => $end_score,
                    'type' => 2,
                    'memo' => $res['name'],
                    'status' => ScoreLog::STATUS_GOODS,
                    'order_id' => $order_id
                ]);
            }

            //发送站内信
            Mail::create([
                'title' => 'Voucher Redeemed',
                'content' => 'You’ve successfully redeemed 【' . $res['name'] . '】using ' . $res['score'] . ' points on 
                【' . date('F j, Y \a\t g:i A', time()) . '.】Please check your voucher section for details.',
                'user_id' => $user['id'],
                'type' => 1,
                'page_type' => 0,
                'jump' => 0,
                'shop_id' => 1,
            ]);
            $user->save();

            Db::commit();
        } catch (Exception $exception) {
            Db::rollback();
            $this->error($exception->getMessage());
        }

        $this->success('success', ['order_id' => $order_id]);
    }



    /**
     * 签到规则
     */
    public function sign_rule()
    {
        $sign_rule = Rule::all();
        $this->success('成功', $sign_rule);
    }

    /**
     * 签到情况
     */
    public function sign_info()
    {
        $user_id = $this->auth->id;
        $res = SignList::where(['user_id' => $user_id])->find();
        if ($res) {
            $res['today_sign'] = 0;
            $last_time = $res['last_time'];
            $today = Time::today();
            if ($last_time > $today[0] && $last_time < $today[1]) {
                $res['today_sign'] = 1;
            }
            if($res['sign_day'] == 7){
                $res['sign_day'] = 0;
            }else {
                $start_time = strtotime(date('Y-m-d 00:00:00', strtotime('-1 day')));
                $end_time = strtotime(date('Y-m-d 23:59:59', strtotime('-1 day')));

                $yesterdaySign = SignList::where(['user_id' => $user_id])
                    ->whereTime('last_time', 'between', [$start_time, $end_time])
                    ->find();
                if(empty($yesterdaySign)){
                    $res['sign_day'] = 0;
                }
            }


        }
        $this->success('成功', $res);
    }

    /**
     * 积分签到
     */
    public function user_sign()
    {
        $user_id = $this->auth->id;
        //签到规则
        $sign_rule = Rule::all();
        $res = SignList::where(['user_id' => $user_id])->find();
        if ($res) {
            $last_time = $res['last_time'];
            $today = Time::today();
            if ($last_time > $today[0] && $last_time < $today[1]) {
                $this->error('Signed in today');
            }
            //正常签到
            $end_sign_day = $res['sign_day'] + 1;
            $score = $sign_rule[$res['sign_day']]['score'];
            $res->last_time = \time();
            $res->sign_day = $end_sign_day;
            $res->save();
        } else {
            SignList::create([
                'user_id' => $user_id,
                'last_time' => \time(),
                'sign_day' => 1,
            ]);
            $score = $sign_rule[0]['score'];
        }
        //用户增加积分及积分记录
        $user = User::where(['id' => $user_id])->find();
        $before = $user['score'];
        $end_score = $user['score'] + $score;
        $user->score = $end_score;
        ScoreLog::create([
            'user_id' => $user_id,
            'score' => $score,
            'before' => $before,
            'after' => $end_score,
            'type' => 1,
            'memo' => 'Checked in',
            'status' => ScoreLog::STATUS_SIGN
        ]);


        $user->save();
        $this->success('success', ['score' => $score]);
    }

    /**
     * 签到礼品列表
     * @ApiMethod (POST)
     * @ApiReturnParams   (name="name", type="text", required=true, description="名称")
     * @ApiReturnParams   (name="score", type="text", required=true, description="积分")
     * @ApiReturnParams   (name="validity", type="text", required=true, description="时效")
     * @ApiReturnParams   (name="lables", type="text", required=true, description="标签")
     * @ApiReturnParams   (name="content", type="text", required=true, description="详情")
     */
    public function sign_goods_list()
    {
        $shop_id = $this->request->header('shopid', 1);
        $res = \app\admin\model\sign\Goods::where(['shop_id' => $shop_id])->order('id desc')->select();
        foreach ($res as &$value) {
            $value['lables'] = explode(',', $value['lables']);
        }
        $this->success('成功', $res);
    }

    /**
     * 签到礼品详情
     * @ApiMethod (POST)
     * @ApiParams   (name="id", type="string", required=true, description="id")
     * @ApiReturnParams   (name="name", type="text", required=true, description="名称")
     * @ApiReturnParams   (name="score", type="text", required=true, description="积分")
     * @ApiReturnParams   (name="validity", type="text", required=true, description="时效")
     * @ApiReturnParams   (name="lables", type="text", required=true, description="标签")
     * @ApiReturnParams   (name="content", type="text", required=true, description="详情")
     */
    public function sign_goods_detail()
    {
        $id = input('post.id');
        $res = \app\admin\model\sign\Goods::where(['id' => $id])->find();
        $res['lables'] = explode(',', $res['lables']);
        $this->success('成功', $res);
    }

    /**
     * 签到积分兑换礼品
     * @ApiMethod (POST)
     * @ApiParams   (name="id", type="string", required=true, description="id")
     */
    public function sign_exchange_goods()
    {
        $id = input('post.id');
        $res = \app\admin\model\sign\Goods::where(['id' => $id])->find();
        $user = User::where(['id' => $this->auth->id])->find();
        if ($res['score'] > $user['sign_score']) {
            $this->error('Insufficient points');
        }
        $order_sn = 'Z' . time() . rand(0, 999);
        if ($res['validity'] != 0) {
            $expire_time = strtotime('+' . $res['validity'] . 'days');
        } else {
            $expire_time = strtotime('+10 year');
        }
        Order::create([
            'order_sn' => $order_sn,
            'shop_id' => $res['shop_id'],
            'user_id' => $this->auth->id,
            'goods_info' => json_encode($res, 256),
            'score' => $res['score'],
            'name' => $res['name'],
            'validity' => $res['validity'],
            'lables' => $res['lables'],
            'content' => $res['content'],
            'type' => 2,
            'image' => $res['image'],
            'expire_time' => $expire_time ?? '',
            'qrcode' => (new \app\api\controller\User())->qrcode($order_sn),
        ]);
        $end_score = $user['score'] - $res['score'];
        $user->sign_score = $end_score;
        UserSignscoreLog::create([
            'user_id' => $this->auth->id,
            'score' => $res['score'],
            'before' => $user['score'],
            'after' => $end_score,
            'type' => 2,
            'memo' => $res['name']
        ]);
        //发送站内信
        Mail::create([
            'title' => 'Voucher Redeemed',
            'content' => 'You’ve successfully redeemed 【' . $res['name'] . '】using ' . $res['score'] . ' points on 【' . date('F j, Y \a\t g:i A', time()) . '.】Please check your voucher section for details.',
            'user_id' => $res['user_id'],
            'type' => 1,
            'page_type' => 0,
            'jump' => 0,
            'shop_id' => 1,
        ]);
        $user->save();
        $this->success('成功');
    }


    /**
     * 已兑换列表
     * @ApiMethod (POST)
     * @ApiParams   (name="type", type="string", required=true, description="1正常商品2签到")
     * @ApiReturnParams   (name="name", type="text", required=true, description="名称")
     * @ApiReturnParams   (name="score", type="text", required=true, description="积分")
     * @ApiReturnParams   (name="validity", type="text", required=true, description="时效")
     * @ApiReturnParams   (name="lables", type="text", required=true, description="标签")
     * @ApiReturnParams   (name="content", type="text", required=true, description="详情")
     * @ApiReturnParams   (name="qrcode", type="text", required=true, description="二维码")
     */
    public function order()
    {
        $type = input('post.type', 1);
        $res = Order::where(['type' => $type, 'is_use' => 0, 'expire_time' => ['>', \time()]])->order('id desc')
            ->where('user_id', $this->auth->id)
            ->select();
        $this->success('成功', $res);
    }

    /**
     * 已兑换订单详情
     * @ApiMethod (POST)
     * @ApiParams   (name="order_sn", type="string", required=true, description="订单号")
     */
    public function order_detail()
    {
        $order_sn = input('post.order_sn',);
        $res = Order::where(['order_sn' => $order_sn])->find();
        $res['lables'] = explode(',', $res['lables']);
        $this->success('成功', $res);
    }


    /**
     * 商城积分记录
     * @ApiMethod (POST)
     * @ApiParams   (name="type", type="string", required=true, description="1增加2减少")
     * @ApiParams   (name="month", type="string", required=true, description="月份")
     * @ApiReturnParams   (name="score", type="text", required=true, description="积分")
     * @ApiReturnParams   (name="before", type="text", required=true, description="变更前积分")
     * @ApiReturnParams   (name="after", type="text", required=true, description="变更后积分")
     * @ApiReturnParams   (name="memo", type="text", required=true, description="备注")
     */
    public function score_log()
    {
        $type = input('post.type', 1);
        $month = input('post.month');
        $start_time = strtotime(date('Y-m-01 00:00:00', strtotime($month)));
        $end_time = strtotime(date('Y-m-t 23:59:59', strtotime($month)));
        $res = ScoreLog::where(['user_id' => $this->auth->id, 'type' => $type, 'createtime' => ['BETWEEN', [$start_time, $end_time]]])->select();
        $this->success('成功', $res);
    }

    /**
     * 签到积分记录
     * @ApiMethod (POST)
     * @ApiParams   (name="type", type="string", required=true, description="1增加2减少")
     * @ApiReturnParams   (name="score", type="text", required=true, description="积分")
     * @ApiReturnParams   (name="before", type="text", required=true, description="变更前积分")
     * @ApiReturnParams   (name="after", type="text", required=true, description="变更后积分")
     * @ApiReturnParams   (name="memo", type="text", required=true, description="备注")
     */
    public function sign_score_log()
    {
        $type = input('post.type', 1);
        $month = input('post.month');
        $start_time = strtotime(date('Y-m-01 00:00:00', strtotime($month)));
        $end_time = strtotime(date('Y-m-t 23:59:59', strtotime($month)));
        $res = UserSignscoreLog::where(['user_id' => $this->auth->id, 'type' => $type, 'createtime' => ['BETWEEN', [$start_time, $end_time]]])->select();
        $this->success('成功', $res);
    }

    /**
     * 联系我们基本信息
     */
    public function contact_message()
    {
        $data['contact_describe'] = config('site.contact_describe');
        $data['contact_phone'] = config('site.contact_phone');
        $data['contact_email'] = config('site.contact_email');
        $data['contact_tk'] = config('site.contact_tk');
        $data['contact_feedbook_url'] = config('site.contact_feedbook_url');
        $data['ins'] = config('site.ins url');
        $this->success('成功', $data);
    }


    /**
     * 联系我们
     * @ApiMethod (POST)
     * @ApiParams   (name="first_name", type="string", required=true, description="姓")
     * @ApiParams   (name="last_name", type="string", required=true, description="名")
     * @ApiParams   (name="email", type="string", required=true, description="邮箱")
     * @ApiParams   (name="content", type="string", required=true, description="内容")
     */
    public function contact_us()
    {
        $first_name = input('post.first_name');
        $last_name = input('post.last_name');
        $email = input('post.email');
        $content = input('post.content');
        Contact::create([
            'user_id' => $this->auth->id,
            'first_name' => $first_name,
            'last_name' => $last_name,
            'email' => $email,
            'content' => $content,
        ]);
        $this->success('成功');
    }

    /**
     * 排队
     * @ApiMethod (POST)
     * @ApiParams   (name="lat", type="string", required=true, description="lat")
     * @ApiParams   (name="lng", type="string", required=true, description="lng")
     * @ApiParams   (name="num", type="string", required=true, description="人数")
     */
    public function line_up()
    {
        $lat = input('post.lat');
        $lng = input('post.lng');
        $num = input('post.num');
        $shop_id = $this->request->header('shopid', 1);
        if (!$lat || !$lng || !$num) {
            $this->error('An error has occurred. Please report this issue to customer service.');
        }
        $shop = Message::where(['id' => $shop_id])->find();
        $line_up_distance = config('site.line_up_distance');
        $earthRadius = 6371; // 地球半径，单位为千米
        $latDiff = deg2rad($lat - $shop['lat']);
        $lonDiff = deg2rad($lng - $shop['lng']);
        $a = sin($latDiff / 2) * sin($latDiff / 2) + cos(deg2rad($lat)) * cos(deg2rad($lng)) * sin($lonDiff / 2) * sin($lonDiff / 2);
        $c = 2 * atan2(sqrt($a), sqrt(1 - $a));
        $distance = $earthRadius * $c;
        if ($distance > $line_up_distance) {
            $this->error('Beyond the distance');
        }
        $tables = Tables::where(['mim_num' => ['<=', $num], 'max_num' => ['>=', $num]])->find();
        $res = Lineup::where(['user_id' => $this->auth->id, 'shop_id' => $shop_id, 'status' => 1])->find();
        if ($res) {
            $this->error('Repeated queuing');
        }
        $line_message = Lineup::where(['table_id' => $tables['id'], 'shop_id' => $shop_id])->order('ranking desc')->find();
        if ($line_message) {
            $ranking = $line_message['ranking'] + 1;
        } else {
            $ranking = 1;
        }
        Lineup::create([
            'user_id' => $this->auth->id,
            'shop_id' => $shop_id,
            'table_id' => $tables['id'],
            'num' => $num,
            'shop_name' => $shop['name'],
            'ranking' => $ranking
        ]);
        $this->success('成功');
    }

    /**
     * 查看排队信息
     * @ApiReturnParams   (name="num", type="text", required=true, description="人数")
     * @ApiReturnParams   (name="shop_name", type="text", required=true, description="店铺名称")
     * @ApiReturnParams   (name="status", type="text", required=true, description="1等待中2成功0失败")
     * @ApiReturnParams   (name="ranking", type="text", required=true, description="排名")
     */
    public function line_message()
    {
        $shop_id = $this->request->header('shopid', 1);
        $res = Lineup::where(['user_id' => $this->auth->id, 'status' => 1, 'shop_id' => $shop_id])->find();
        if ($res) {
            $res['table_message'] = Tables::where(['id' => $res['table_id']])->find();
            $res['table_code'] = $res['table_message']['name'] . $res['id'];
        }
        $this->success('成功', $res);
    }

    /**
     * Notes: 消费次数
     * User: chenLei
     * Date: 8/25/25
     * @throws Exception
     * @throws \think\db\exception\DataNotFoundException
     * @throws \think\db\exception\ModelNotFoundException
     * @throws \think\exception\DbException
     */
    public function levelExp()
    {
        $userModel = new User();
        $count = $userModel->xfCount($this->auth->id);

        $level = Levels::where('level', '>', 1)->field('level,name,buy_number')->select();

        $data = [
            'user_level' => $userModel->where('id', $this->auth->id)->value('level'),
            'count' => $count,
            'level' => $level
        ];
        $this->success('success', $data);
    }

    /**
     * Notes: 用户降级 处理
     * User: chenLei
     * Date: 8/26/25
     */
    public function downgrade()
    {
        $userModel = new User();
        $userModel->downgrade();
        $this->success('success');
    }


    /**
     * Notes: 查询用户当月生日
     * User: chenLei
     * Date: 8/26/25
     * @throws \think\db\exception\DataNotFoundException
     * @throws \think\db\exception\ModelNotFoundException
     * @throws \think\exception\DbException
     */
    public function checkBirthday()
    {
        $userModel = new User();
        $userModel->checkBirthday();

        $this->success();
    }
}
